/*
 * @Date: 2024-08-12 11:39:52
 * @LastEditors: 陈俊宇 467724386@qq.com
 * @LastEditTime: 2024-10-22 09:10:20
 */
export function debounce(func, wait, immediate) {
    let timeout, args, context, timestamp, result

    const later = function () {
        // 据上一次触发时间间隔
        const last = +new Date() - timestamp

        // 上次被包装函数被调用时间间隔 last 小于设定时间间隔 wait
        if (last < wait && last > 0) {
            timeout = setTimeout(later, wait - last)
        } else {
            timeout = null
            // 如果设定为immediate===true，因为开始边界已经调用过了此处无需调用
            if (!immediate) {
                result = func.apply(context, args)
                if (!timeout) context = args = null
            }
        }
    }
    return function (...args) {
        context = this
        timestamp = +new Date()
        const callNow = immediate && !timeout
        // 如果延时不存在，重新设定延时
        if (!timeout) timeout = setTimeout(later, wait)
        if (callNow) {
            result = func.apply(context, args)
            context = args = null
        }

        return result
    }
}

/**
 * 判断文件类型
 *
 * @param extension 文件扩展名
 * @returns 返回文件类型，包括'image'、'video'和'file'
 */
export function determineFileType(extension) {
    // 文件类型映射表
    const fileTypeMap = {
        jpg: 'image',
        jpeg: 'image',
        png: 'image',
        gif: 'image',
        bmp: 'image',
        webp: 'image',
        ico: 'image',
        tiff: 'image',

        mp4: 'video',
        avi: 'video',
        mkv: 'video',
        mov: 'video',
        wmv: 'video',
        flv: 'video',
        webm: 'video',
        mpeg: 'video',
        mpg: 'video',
        m4v: 'video',

        // 默认为文件
        default: 'file',
    }

    const fileType = fileTypeMap[extension.toLowerCase()] || fileTypeMap.default

    // 返回文件类型，使用映射表的default属性作为默认值
    return fileType
}

/**
 * 获取图片的宽度和高度
 * @param {File} file - 图片文件对象
 * @returns {Promise} - 返回一个Promise，该Promise在解析时包含图片的宽度和高度
 */
export function getImageWh(file) {
    return new Promise((resolve, reject) => {
        const reader = new FileReader()
        reader.onload = (e) => {
            const img = new Image()
            img.onload = () => {
                const width = img.naturalWidth
                const height = img.naturalHeight
                resolve({ width, height }) // 解析Promise并返回宽度和高度
            }
            img.onerror = reject // 如果图片加载失败，拒绝Promise
            img.src = e.target.result
        }
        reader.readAsDataURL(file)
    })
}

/**
 * 获取视频文件的宽度、高度和时长
 *
 * 此函数通过创建一个视频元素并预加载其元数据来获取视频的宽度、高度和时长
 * 它使用Promise来处理异步操作，确保在视频元数据加载完成后才获取信息
 *
 * @param {File} file 视频文件对象，应为File API返回的文件对象
 * @returns {Promise} 返回一个Promise对象，该Promise在视频元数据加载成功后解析，解析值包含宽度、高度和时长
 */
export function getVideoWh(file) {
    return new Promise((resolve, reject) => {
        const video = document.createElement('video')
        video.preload = 'metadata' // 预加载元数据
        video.onloadedmetadata = () => {
            const width = video.videoWidth
            const height = video.videoHeight
            const duration = video.duration
            resolve({ width, height, duration }) // 解析Promise并返回宽度、高度和时长
        }
        video.onerror = reject // 如果加载失败，拒绝Promise
        video.src = URL.createObjectURL(file) // 使用createObjectURL创建一个指向文件的URL
    })
}
